/*
 * Copyright (c) Huawei Technologies Co., Ltd. 2021-2023. All rights reserved.
 * Description: UDK lcore interface
 * Author: -
 * Create: 2021.7.20
 */

#ifndef UDK_LCORE_H
#define UDK_LCORE_H

#include <stdint.h>

#include "udk_common.h"
#include "udk_spinlock.h"

/* per thread(lcore) variable define */
#define UDK_DEFINE_PER_LCORE(type, name) __thread __typeof__(type) per_lcore_##name
/* per thread(lcore) variable decleare */
#define UDK_DECLEARE_PRE_LCORE(type, name) extern __thread __typeof__(type) per_lcore_##name
/* per thread(lcore) variable */
#define UDK_PER_LCORE(name) (per_lcore_##name)

#define UDK_LCORE_ID_ANY ((uint32_t)(-1))

UDK_DECLEARE_PRE_LCORE(uint32_t, udk_lcore_id);
extern uint32_t g_udk_lcore_id;
extern udk_spinlock_t lcore_id_lock;

static inline uint32_t udk_get_curr_lcore_id(void)
{
    uint32_t lcore_id;

    udk_spinlock_lock(&lcore_id_lock);

    if (g_udk_lcore_id >= UDK_MAX_LCORE) {
        lcore_id = UDK_LCORE_ID_ANY;
    } else {
        lcore_id = g_udk_lcore_id++;
    }

    udk_spinlock_unlock(&lcore_id_lock);

    return lcore_id;
}

static inline uint32_t udk_lcore_id(void)
{
    if (UDK_PER_LCORE(udk_lcore_id) == UDK_LCORE_ID_ANY) {
        UDK_PER_LCORE(udk_lcore_id) = udk_get_curr_lcore_id();
    }

    return UDK_PER_LCORE(udk_lcore_id);
}

int udk_lcore_init(void);

#endif